package com.wskj.common.utils.tencent;

import cn.hutool.core.collection.ListUtil;
import cn.hutool.core.map.MapUtil;
import cn.hutool.core.net.url.UrlBuilder;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.extra.servlet.ServletUtil;
import cn.hutool.json.JSONUtil;
import com.google.common.collect.Maps;
import com.wskj.common.utils.common.AssertUtils;
import com.wskj.common.utils.common.HttpUtils;
import com.wskj.common.utils.common.JsonUtils;
import com.wskj.common.utils.common.ServletUtils;
import com.wskj.common.utils.tencent.bean.ImApiResponse;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.compress.utils.Lists;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;

/**
 * 即时通信 工具类
 *
 * @author Kun
 * @date 2021/11/09
 */
@Slf4j
public class ImUtils {

    public static final String RESULT_OK = "OK";

    /**
     * 腾讯Im基础地址
     */
    public static final String BASE_URL = "adminapisgp.im.qcloud.com";
    // public static final String BASE_URL = "console.tim.qq.com";
    /**
     * 腾讯IM版本号
     */
    public static final String VERSION = "v4";

    /** 在线状态 */
    public static final String ON_LINE="State.StateChange";

    /**
     * 群组类型：直播群
     */
    private static final String GROUP_TYPE = "AVChatRoom";

    /**
     * 校验用户是否导入IM
     */
    public static ImApiResponse checkInIm(Long sdkAppId, String imKey, String identifier, Object userId) {
        String serviceName = "im_open_login_svc";
        String command = "account_check";
        Map<String, Object> body = Maps.newHashMap();
        ArrayList<Map<String, String>> items = Lists.newArrayList();
        items.add(MapUtil.of("UserID", String.valueOf(userId)));
        body.put("CheckItem", items);
        String result = HttpUtils.sendJsonData(getUrl(sdkAppId,imKey,identifier, serviceName, command), JsonUtils.toJsonString(body));
        ImApiResponse response = Optional.ofNullable(JSONUtil.toBean(result, ImApiResponse.class)).orElse(new ImApiResponse());
        AssertUtils.isTrue(Objects.equals(response.getActionStatus(), RESULT_OK), "用户信息导入IM查询失败！");
        return response;
    }

    /**
     * 用户信息导入IM
     */
    public static void impUser(Long sdkAppId,String imKey,String identifier,Object userId,String nickName,String avatar) {
        String serviceName = "im_open_login_svc";
        String command = "account_import";
        Map<String, Object> body = Maps.newHashMap();
        body.put("UserID", String.valueOf(userId));
        body.put("Nick", nickName);
        body.put("FaceUrl", avatar);
        String url = getUrl(sdkAppId,imKey,identifier, serviceName, command);
        String result = HttpUtils.sendJsonData(url, JsonUtils.toJsonString(body));
        ImApiResponse response = Optional.ofNullable(JSONUtil.toBean(result, ImApiResponse.class)).orElse(new ImApiResponse());
        AssertUtils.isTrue(Objects.equals(response.getActionStatus(), RESULT_OK), "导入用户失败！");
        log.debug("导入用户信息; UserId: {}", userId);
    }

    /**
     * 创建群聊天
     * @param sdkAppId  配置参数
     * @param imKey  配置参数
     * @param identifier  配置参数
     * @param groupId 群组ID
     * @param userId 所有者
     * @param groupName    群聊名称
     */
    public static void createGroup(Long sdkAppId,String imKey,String identifier, Object groupId,String groupName,Object userId, String nickName,String avatar) {
        impUser(sdkAppId,imKey,identifier,userId,nickName,avatar);
        String serviceName = "group_open_http_svc";
        String command = "create_group";
        String url = getUrl(sdkAppId,imKey,identifier, serviceName, command);
        Map<String, Object> body = Maps.newHashMap();
        body.put("GroupId", String.valueOf(groupId));
        body.put("Owner_Account", String.valueOf(userId));
        body.put("Type", GROUP_TYPE);
        body.put("Name", groupName);
        String result = HttpUtils.sendJsonData(url, JsonUtils.toJsonString(body));
        ImApiResponse response = Optional.ofNullable(JSONUtil.toBean(result, ImApiResponse.class)).orElse(new ImApiResponse());
        AssertUtils.isTrue(Objects.equals(response.getActionStatus(), RESULT_OK), "创建群组失败！");
        log.info("创建直播群聊; GroupId: {}, Owner:{},  Result:{}", groupId, userId, result);
    }

    /**
     * 销毁群聊
     */
    public static void destroyGroup(Long sdkAppId,String imKey,String identifier, Object groupId) {
        String serviceName = "group_open_http_svc";
        String command = "destroy_group";
        String url = getUrl(sdkAppId,imKey,identifier, serviceName, command);
        Map<String, Object> body = Maps.newHashMap();
        body.put("GroupId", String.valueOf(groupId));
        String result = HttpUtils.sendJsonData(url, JsonUtils.toJsonString(body));
        ImApiResponse response = Optional.ofNullable(JSONUtil.toBean(result, ImApiResponse.class)).orElse(new ImApiResponse());
        // AssertUtils.isTrue(Objects.equals(response.getActionStatus(), RESULT_OK), "解散群组失败！");
        log.error("群组:"+groupId+"解散群组失败！");
        log.info("解散直播群聊; GroupId: {}, UserId:{},  Result:{}", groupId, 0L, result);
    }

    /**
     * 获取群详细资料
     */
    public static ImApiResponse getGroupInfo(Long sdkAppId,String imKey,String identifier, Object groupId) {
        String serviceName = "group_open_http_svc";
        String command = "get_group_info";
        Map<String, Object> body = Maps.newHashMap();
        body.put("GroupIdList", ListUtil.of(Objects.toString(groupId)));
        String result = HttpUtils.sendJsonData(getUrl(sdkAppId,imKey,identifier, serviceName, command), JsonUtils.toJsonString(body));
        ImApiResponse response = Optional.ofNullable(JSONUtil.toBean(result, ImApiResponse.class)).orElse(new ImApiResponse());
        log.debug("获取直播群详细信息; groupId: {}", groupId);
        return response;
    }

    /**
     * 腾讯IM回调时校验参数
     * @param sdkAppId sdkAppId
     */
    public static ImApiResponse validRequest(String sdkAppId) {
        HttpServletRequest request = ServletUtils.getRequest();
        Map<String, String> paramMap = ServletUtil.getParamMap(request);
        if (Objects.equals(String.valueOf(sdkAppId), paramMap.get("SdkAppId"))) {
            ImApiResponse.fail("SdkAppId不合法！");
            return ImApiResponse.fail("SdkAppId不合法！");
        }
        return ImApiResponse.ok();
    }

    private static String getUrl(Long sdkAppId,String imKey,String identifier,String serviceName, String command) {
        TLSSigAPIv2 apIv2 = new TLSSigAPIv2(sdkAppId, imKey);
        return UrlBuilder.create()
                .setScheme("https")
                .setHost(BASE_URL)
                .addPath(VERSION)
                .addPath(serviceName)
                .addPath(command)
                .addQuery("sdkappid", String.valueOf(sdkAppId))
                .addQuery("identifier", identifier)
                .addQuery("usersig", apIv2.genUserSig(identifier, 600))
                .addQuery("random", RandomUtil.randomNumbers(32))
                .addQuery("contenttype", "json")
                .build();
    }
}
